package cn.iocoder.yudao.module.ordering.service.food;

import cn.hutool.core.date.LocalDateTimeUtil;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.framework.web.core.util.WebFrameworkUtils;
import cn.iocoder.yudao.module.ordering.constant.Constants;
import cn.iocoder.yudao.module.ordering.controller.admin.food.vo.FoodPageReqVO;
import cn.iocoder.yudao.module.ordering.controller.admin.food.vo.FoodRespVO;
import cn.iocoder.yudao.module.ordering.controller.admin.food.vo.FoodSaveReqVO;
import cn.iocoder.yudao.module.ordering.controller.admin.food.vo.MyOrderingReqVO;
import cn.iocoder.yudao.module.ordering.controller.admin.food.vo.MyOrderingRespVO;
import cn.iocoder.yudao.module.ordering.dal.dataobject.food.FoodDO;
import cn.iocoder.yudao.module.ordering.dal.dataobject.record.RecordDO;
import cn.iocoder.yudao.module.ordering.dal.mysql.food.FoodMapper;
import cn.iocoder.yudao.module.ordering.dal.mysql.record.RecordMapper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.validation.annotation.Validated;

import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.iocoder.yudao.module.ordering.enums.ErrorCodeConstants.FOOD_NOT_EXISTS;

/**
 * 订餐-餐品信息 Service 实现类
 *
 * @author 芋道源码
 */
@Service
@Validated
@Slf4j
public class FoodServiceImpl implements FoodService {

    @Resource
    private FoodMapper foodMapper;
    @Resource
    private RecordMapper recordMapper;

    @Override
    public Long createFood(FoodSaveReqVO createReqVO) {
        // 插入
        FoodDO food = BeanUtils.toBean(createReqVO, FoodDO.class);
        foodMapper.insert(food);
        // 返回
        return food.getId();
    }

    @Override
    public void updateFood(FoodSaveReqVO updateReqVO) {
        // 校验存在
        validateFoodExists(updateReqVO.getId());
        // 更新
        FoodDO updateObj = BeanUtils.toBean(updateReqVO, FoodDO.class);
        foodMapper.updateById(updateObj);
    }

    @Override
    public void deleteFood(Long id) {
        // 校验存在
        validateFoodExists(id);
        // 删除
        foodMapper.deleteById(id);
    }

    private void validateFoodExists(Long id) {
        if (foodMapper.selectById(id) == null) {
            throw exception(FOOD_NOT_EXISTS);
        }
    }

    @Override
    public FoodDO getFood(Long id) {
        return foodMapper.selectById(id);
    }

    @Override
    public PageResult<FoodDO> getFoodPage(FoodPageReqVO pageReqVO) {
        return foodMapper.selectPage(pageReqVO);
    }


    /**
     * 根据请求获取我的订餐列表。
     * 该方法首先查询所有的订餐记录，然后筛选出当前可订餐的菜品，接着获取员工已订过的菜品，
     * 最后将可订餐菜品和已订餐菜品合并，并去除重复项，返回合并后的订餐列表。
     *
     * @param reqVO 请求参数对象，目前未使用，预留以备后续扩展。
     * @return 返回合并后的订餐列表，包含可订餐菜品和已订餐菜品。
     */
    @Override
    public List<MyOrderingRespVO> getMyOrderingList(MyOrderingReqVO reqVO) {
        // 查询当前员工所有的订餐记录
        RecordDO recordParams = new RecordDO();
        recordParams.setUserId(WebFrameworkUtils.getLoginUserId());
        recordParams.setStatusList(Arrays.asList(Constants.RECORD_STATUS_ORDERED, Constants.RECORD_STATUS_SEND,
                Constants.RECORD_STATUS_RECEIVED));
        List<RecordDO> recordList = recordMapper.selectListCommon(recordParams);

        // 查询当前可订餐的菜品
        FoodDO foodParams = new FoodDO();
        foodParams.setOrderDate(LocalDateTimeUtil.now());
        foodParams.setStatus(Constants.FOOD_STATUS_ON_SALE);
        foodParams.setTypeOrderByAsc(true);
        List<FoodDO> canOrderList = foodMapper.selectListCommon(foodParams);

        // 封装订餐列表
        List<MyOrderingRespVO> returnList = new ArrayList<>();
        LocalDateTime start = reqVO.getOrderDates()[0];
//        LocalDateTime index = reqVO.getOrderDates()[0];
        LocalDateTime end = reqVO.getOrderDates()[1];
        for(int i = 1; start.isBefore(end); start = start.plusDays(i++)){
            MyOrderingRespVO tempOrdering = new MyOrderingRespVO();
            tempOrdering.setOrderDate(start);
            List<FoodRespVO> foodList = new ArrayList<>();
            LocalDateTime finalStart = start;
            canOrderList.forEach(item -> {
                if(LocalDateTimeUtil.isIn(finalStart, item.getDateStart(), item.getDateEnd())){
                    RecordDO hasOrderRecord = recordList.stream().filter(record ->
                            record.getFoodId().equals(item.getId())
                            && LocalDateTimeUtil.isSameDay(record.getOrderDate(), finalStart))
                            .findFirst().orElse(null);
                    // 首先检查hasOrderRecord是否为null
                    if(hasOrderRecord != null) {
                        // 如果hasOrderRecord非null，则设置对应的值
                        item.setHasOrdered(true);
                        item.setRecordId(hasOrderRecord.getId());
                    } else {
                        // 如果hasOrderRecord为null，则设置相应的默认值
                        item.setHasOrdered(false);
                    }
                    foodList.add(BeanUtils.toBean(item, FoodRespVO.class));
                }
            });
            tempOrdering.setFoodList(foodList);
            returnList.add(tempOrdering);
        }
        // 封装数据后返回
        return returnList;
    }

}
